package vacuum.flatgrass;

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.RandomAccessFile;
import java.util.ArrayList;
import java.util.LinkedList;

import org.bukkit.WorldCreator;

public class FileManager
{
	private static final char END_WORLD_NAME = '/';
	private static final char END_CONFIG = '\n';
	private File dataDir;
	private File worldList;
	public FileManager(File dir){
		dataDir = new File(dir.toString());
		dataDir.mkdirs();
		worldList = new File(dataDir.toString() + File.separatorChar + "worlds.txt");
		if(!worldList.exists())
			try
		{
				worldList.createNewFile();
		} catch (IOException e)
		{
			e.printStackTrace();
		}
	}

	public WorldCreator[] loadWorlds() throws IOException{
		FileInputStream fis = new FileInputStream(worldList);
		LinkedList<WorldCreator> ll = new LinkedList<WorldCreator>();
		int i;
		ArrayList<Byte> heights = null;
		ArrayList<Byte> blocks = null;
		String s = "";
		boolean isName = true;
		while((i = fis.read()) != -1){
			if(isName){
				if(END_WORLD_NAME == (char)i){
					isName = false;
					heights = new ArrayList<Byte>();
					blocks = new ArrayList<Byte>();
					System.out.println("[FlatGrass] Loading world generator <" + s + ">.");
				} else {
					s += (char)i;
				}
			} else {
				if (END_CONFIG == (char)i){
					System.out.println("[FlatGrass] Loaded world generator <" + s + ">!");
					WorldCreator wc = new WorldCreator(s);
					wc.generator(FlatGrass.getGenerator(convertByteArrayTobyteArray(blocks.toArray(new Byte[0])), convertByteArrayTobyteArray(heights.toArray(new Byte[0]))));
					s = "";
					ll.add(wc);
					isName = true;
				} else {
					byte block = (byte) (i & 0xFF);
					byte height = (byte) (fis.read() & 0xFF);
					System.out.println("[FlatGrass] <" + s + "> begin placing " + block + " after " + height);
					heights.add(height);
					blocks.add(block);
				}
			}
		}
		fis.close();
		return ll.toArray(new WorldCreator[0]);
	}

	private byte[] convertByteArrayTobyteArray(Byte[] array)
	{
		byte[] ret = new byte[array.length];
		for (int i = 0; i < ret.length; i++)
		{
			ret[i] = (byte)array[i];
		}
		return ret;
	}

	public WorldCreator addWorld(String name, byte[] blocks, byte[] heights) throws IOException{
		removeWorld(name);
		System.out.println("[FlatGrass] Writing to file.");
		FileOutputStream fos = new FileOutputStream(worldList, true);
		for(char c : name.toCharArray()){
			fos.write((int)c);
		}
		fos.write((int)END_WORLD_NAME);
		for (int i = 0; i < heights.length; i++)
		{
			System.out.println("[FlatGraass] Writing " + blocks[i] + " and " + heights[i]);
			fos.write(blocks[i]);
			fos.write(heights[i]);
		}
		fos.write((int)END_CONFIG);
		
		fos.close();

		System.out.println("[FlatGrass] Generating world creator.");
		WorldCreator wc = new WorldCreator(name);
		wc.generator(FlatGrass.getGenerator(blocks, heights));
		return wc;
	}

	public boolean removeWorld(String name) throws IOException{
		System.out.println("[FlatGrass] Attempting to remove world " + name + "...");
		RandomAccessFile raf = new RandomAccessFile(worldList, "rw");
		int i = 0;
		StringBuffer buf = new StringBuffer();
		boolean isName = true;
		long pos = -1;
		while((i = raf.read()) != -1){
			if(END_WORLD_NAME == (char)i){
				isName = false;
				System.out.println("Comparing " + buf.toString() + " to " + name);
				if(buf.toString().equalsIgnoreCase(name)){
					pos = raf.getFilePointer() - buf.length();
				}
			} else if (END_CONFIG == (char)i){
				isName = true;
				buf = new StringBuffer();
			} else if (isName){
				buf.append((char)i);
			}
		}
		if(pos == -1){
			System.out.println("[FlatGrass] " + name + " is not an existing world.");
			raf.close();
			return false;
		}
		
		System.out.println("[FlatGrass] Removing world " + name);
		
		while((i = raf.read()) != -1){
			if(END_CONFIG == (char)i){
				break;
			}
		}
		
		while((i = raf.read()) != -1){
			buf.append((char)i);
		}
		
		raf.setLength(pos + 1);
		raf.seek(pos);
		for(char c : buf.toString().toCharArray()){
			raf.write(c & 0xFF);
		}
		raf.close();
		
		return true;
		
	}

}
